﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
using System.Net;

//http://www.switchonthecode.com/tutorials/csharp-tutorial-simple-threaded-tcp-server

namespace XDLogonMonitor {
    class TCPServer {
        private System.Net.Sockets.TcpListener tcpListener;
        private System.Threading.Thread listenThread;

        public TCPServer() {
            tcpListener = new System.Net.Sockets.TcpListener(IPAddress.Any, 80);
            listenThread = new Thread(new ThreadStart(WaitForClients));
            listenThread.Start();
        }
        private void WaitForClients() {
            tcpListener.Start();
            while (true) {
                try {
                    System.Net.Sockets.TcpClient client = tcpListener.AcceptTcpClient(); //THIS WILL BLOCK
                    System.Threading.Thread clientThread = new Thread(new ParameterizedThreadStart(ClientCommunication));
                    clientThread.Start(client);
                }
                catch (Exception e) {
                    Console.Error.WriteLine(e.Message);
                }
            }
        }


        /* _DESKTOP_SERVICE_
         * Connect Port 80 to Monitor Server
         * Send "READY: <COMPUTERNAME>"
         * Read Event Log, when 528, Send "EVENT: <TIME>"
         * Check if explorer.exe is running, Send "EXPLORER: <TIME>"
         * Check if cmd.exe is running, Send "STARTUP: <TIME>"
         * 
         */
        //http://msdn.microsoft.com/en-us/library/system.net.sockets.networkstream.read.aspx
        private void ClientCommunication(object client) {

            Byte[] buffer = new Byte[4096];
            int bytesRead = 0;
            bytesRead = 0;
            String desktopName = "";
            long EventNum = 0;
            System.Net.Sockets.TcpClient tcpClient = (System.Net.Sockets.TcpClient)client;
            System.Net.Sockets.NetworkStream networkStream = tcpClient.GetStream();


            if (networkStream.CanRead) {
                do {
                    bytesRead = networkStream.Read(buffer, 0, 4096); //THIS WILL BLOCK
                    //if (bytesRead == 0) break;

                    ASCIIEncoding encoder = new ASCIIEncoding();
                    String message = encoder.GetString(buffer, 0, bytesRead);
                    if (message.Contains("READY")) {
                        String[] splitMessage = message.Split(':');
                        desktopName = splitMessage[1];
                        //DesktopProcessThread dpt = new DesktopProcessThread(desktopName);
                        //EventNum = dpt.EventNum;
                    }
                    else if (message.Contains("EVENT")) {
                        String[] splitMessage = message.Split(':');
                        String eventTime = splitMessage[1];
                        Database d = new Database(EventNum);
                        d.AddEventRow(EventNum, (Int16)(EventTypes.EVENT_LOG_TIME), DateTime.Parse(eventTime), desktopName);
                    }
                } while (networkStream.DataAvailable);
            }
        }
    }
}
